﻿using System;
using System.Collections.Generic;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Content.Pipeline.Serialization;

namespace Natur.MapManager
{
    public class MapData
    {
        public SectorData[] arySectorData;

        public MapData() { }

        public MapData(SectorData[] newSectors)
        { arySectorData = newSectors; }
    }

    public class SectorData
    {
        public CustomVD[] Vertices;
        public Int16[] Indices;

        [ContentSerializer(Optional = true)] public CustomVD[] DVertices;
        [ContentSerializer(Optional = true)] public Int16[] DIndices;
        
        public int TextureIndex;

        public AnimationData[] Animations;
        public TriggerData[] Triggers;

        public LightData[] Lights;
        public LocationData[] Locations;

        [ContentSerializer(Optional=true)] public RelayData[] Relays;
        public SpawnData[] Spawns;

        public BoundData[] Bounds;
        public StructureData[] Structures;
        public PinnedData[] PinnedStructures;

        public SectorData() { }

        public SectorData(CustomVD[] newVerts, Int16[] newInds, CustomVD[] newDVerts, Int16[] newDInds, int newTextureIndex, AnimationData[] newAnimations, TriggerData[] newTriggers,
            LightData[] newLights, LocationData[] newLocations, RelayData[] newRelays, SpawnData[] newSpawns, BoundData[] newBounds, StructureData[] newStructures, PinnedData[] newPinned)
        {
            Vertices = newVerts; Indices = newInds;
            DVertices = newDVerts; DIndices = newDInds;
            TextureIndex = newTextureIndex;

            Animations = newAnimations;
            Triggers = newTriggers;
            Lights = newLights;
            Locations = newLocations;
            Relays = newRelays;
            Spawns = newSpawns;
            Bounds = newBounds;
            Structures = newStructures;
            PinnedStructures = newPinned;
        }
    }

    public class AnimationData
    {
        public int ID;
        public int PlayMode;
        public float Duration;
        public float Speed;
        public bool Repeat;

        public int[] SelectedObjects;
        public FrameData[] aryFrames;

        public AnimationData() { }

        public AnimationData(int newID, int newPlayMode, float newDuration, float newSpeed, bool isRepeat, int[] newSelected, FrameData[] newFrames)
        {
            ID = newID;
            PlayMode = newPlayMode;
            Duration = newDuration;
            Speed = newSpeed;
            Repeat = isRepeat;
            SelectedObjects = newSelected;
            aryFrames = newFrames;
        }
    }

    public class FrameData
    {
        public int ID;
        public float TimePosition;
        public StateData[] aryStates;

        public FrameData() { }

        public FrameData(int newID, float newTimePosition, StateData[] newStates)
        { ID = newID; TimePosition = newTimePosition; aryStates = newStates; }
    }

    public class StateData
    {
        public Vector3 Position;
        public Vector3 Forward;
        public Vector3 Up;

        public StateData() { }

        public StateData(Vector3 newPosition, Vector3 newForward, Vector3 newUp)
        { Position = newPosition; Forward = newForward; Up = newUp; }
    }

    public class TriggerData
    {
        public int ID;
        public int TargetObject;
        public int Occurrences;
        public int CommandIndex;
        public int LocationIndex;
        public float Delay;

        public TriggerData() { }

        public TriggerData(int newID, int newTargetObject, int newOccurrences, int newCommandIndex, int newLocationIndex, float newDelay)
        {
            ID = newID;
            TargetObject = newTargetObject;
            Occurrences = newOccurrences;
            CommandIndex = newCommandIndex;
            LocationIndex = newLocationIndex;
            Delay = newDelay;
        }
    }

    public class LightData
    {
        public int ID;
        public Vector3 Position;
        public Vector3 Forward;
        public Vector3 Up;
        public Color Color;
        public float Intensity;
        public float Range;

        public LightData() { }

        public LightData(int newID, Vector3 newPosition, Vector3 neForward, Vector3 newUp, Color newColor, float newIntensity, float newRange)
        { ID = newID; Position = newPosition; Forward = neForward; Up = newUp; Color = newColor; Intensity = newIntensity; Range = newRange; }
    }

    public class LocationData
    {
        public int ID;
        public Vector3 Position;
        public Vector3 Forward;
        public Vector3 Up;
        public float DimensionRoW;
        public float DimensionH;
        public float DimensionD;

        public LocationData() { }

        public LocationData(int newID, Vector3 newPosition, float newRadius)
        { ID = newID; Position = newPosition; Forward = Vector3.Forward; Up = Vector3.Up; DimensionRoW = newRadius; }

        public LocationData(int newID, Vector3 newPosition, Vector3 newForward, Vector3 newUp, float newW, float newH, float newD)
        {
            ID = newID;
            Position = newPosition; Forward = newForward; Up = newUp;
            DimensionRoW = newW; DimensionH = newH; DimensionD = newD;
        }
    }

    public class RelayData
    {
        public int ID;
        public Vector3 Position;
        public int[] aryLinked;

        public RelayData() { }

        public RelayData(int newID, Vector3 newPos, int[] newLinked)
        {
            ID = newID;
            Position = newPos;
            aryLinked = newLinked;
        }
    }

    public class SpawnData
    {
        public int ID;
        public int SpawnID;
        public Vector3 Position;
        public int Count;
        public float Delay;

        public SpawnData() { }

        public SpawnData(int newID, int newSpawnID, Vector3 newPos, int newCount, float newDelay)
        {
            ID = newID;
            SpawnID = newSpawnID;
            Position = newPos;
            Count = newCount;
            Delay = newDelay;
        }
    }

    public class StructureData
    {
        public int ID;
        public Vector3 Position;
        public Vector3 Forward;
        public Vector3 Up;

        public int StartVertex;
        public int VertexCount;
        public int StartIndex;
        public int IndexCount;

        public float WRadius;
        public float HRadius;
        public float DRadius;

        public Vector2 TexStart;
        public Vector2 TexDimension;

        public BoundType BoundType;
        public bool IsInteractive;

        public StructureData() { }

        public StructureData(int newID, Vector3 newPosition, Vector3 newForward, Vector3 newUp, float newWRadius, float newHRadius, float newDRadius,
            int newStartVertex, int newVertexCount, int newStartIndex, int newIndexCount, Vector2 newTexStart, Vector2 newTexDimension, BoundType newBoundType, bool isInteractive)
        {
            ID = newID;
            Position = newPosition; Forward = newForward; Up = newUp;
            StartVertex = newStartVertex; VertexCount = newVertexCount;
            StartIndex = newStartIndex; IndexCount = newIndexCount;
            WRadius = newWRadius; HRadius = newHRadius; DRadius = newDRadius;
            TexStart = newTexStart; TexDimension = newTexDimension;
            BoundType = newBoundType;
            IsInteractive = isInteractive;
        }
    }

    public class BoundData
    {
        public int ID;
        public Vector3 Position;
        public Vector3 Forward;
        public Vector3 Up;
        public float[] aryDimensions;
        [ContentSerializer(Optional = true)] public bool IsLadder;

        public BoundData() { }

        public BoundData(int newID, Vector3 newPosition, bool isLadder, float newDimensions)
        {
            ID = newID;
            Position = newPosition; Forward = Vector3.Forward; Up = Vector3.Up;
            IsLadder = isLadder;
            aryDimensions = new float[1]; aryDimensions[0] = newDimensions;
        }

        public BoundData(int newID, Vector3 newPosition, Vector3 newForward, Vector3 newUp, bool isLadder, params float[] newDimensions)
        {
            ID = newID;
            Position = newPosition; Forward = newForward; Up = newUp;
            IsLadder = isLadder;
            aryDimensions = newDimensions;
        }
    }

    public class PinnedData
    {
        public int ID;
        public Vector3 Position;
        public Vector3 Forward;
        public Vector3 Up;
        public int[] PinnedObjects;

        public PinnedData() { }

        public PinnedData(int newID, Vector3 newPos, Vector3 newForward, Vector3 newUp, int[] newStructureIndices)
        {
            ID = newID;
            Position = newPos; Forward = newForward; Up = newUp;
            PinnedObjects = newStructureIndices;
        }
    }
}
